package com.dingup.provider.service.lesson.impl;

import com.alibaba.fastjson.JSONObject;
import com.dingup.api.bean.page.PageData;
import com.dingup.api.bean.requestBean.lesson.LessonPageBean;
import com.dingup.api.enums.ExamTypeEnum;
import com.dingup.api.model.lesson.LessonInfo;
import com.dingup.api.model.lesson.LessonSubjectInfo;
import com.dingup.provider.controller.lesson.LessonController;
import com.dingup.provider.mapper.LessonInfoMapper;
import com.dingup.provider.mapper.LessonSubjectInfoMapper;
import com.dingup.provider.service.lesson.LessonService;
import com.dingup.provider.service.lesson.LessonSubjectInfoService;
import com.dingup.provider.util.PageDataUtil;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.*;
import java.util.stream.Collectors;

/**
 * Created by wancheng on 2018/8/23.
 */
@Service
public class LessonServiceImpl implements LessonService {

    private static Logger logger = LoggerFactory.getLogger(LessonServiceImpl.class);

    @Autowired
    LessonInfoMapper lessonInfoMapper;
    @Autowired
    LessonSubjectInfoMapper lessonSubjectInfoMapper;
    @Autowired
    LessonSubjectInfoService lessonSubjectInfoService;

    @Override
    public LessonInfo getLessonInfoById(Integer id) {
        LessonInfo lessonInfo = lessonInfoMapper.selectByPrimaryKey(id);
        List<LessonSubjectInfo> lessonSubjectInfos = lessonSubjectInfoMapper.getByLessonId(id);
        Collections.sort(lessonSubjectInfos, new Comparator<LessonSubjectInfo>() {
            @Override
            public int compare(LessonSubjectInfo o1, LessonSubjectInfo o2) {
                return o1.getOrder() - o2.getOrder();
            }
        });
        if (lessonInfo != null) {
            lessonInfo.setSubjectInfos(lessonSubjectInfos);
        }
        return lessonInfo;
    }

    @Override
    public LessonInfo getLessonInfoByLessonName(String lessonName) {
        return lessonInfoMapper.getByLessonName(lessonName);
    }

    @Override
    @Transactional
    public LessonInfo saveLessonInfo(LessonInfo lessonInfo) {
        logger.info("保存课程信息 lessonInfo={}", JSONObject.toJSONString(lessonInfo));
        lessonInfoMapper.insertSelective(lessonInfo);
        if (lessonInfo.getSubjectInfos() != null) {
            lessonInfo.getSubjectInfos().stream().forEach(
                    lessonSubjectInfo -> {
                        lessonSubjectInfo.setLessonId(lessonInfo.getId());
                        lessonSubjectInfoMapper.insertSelective(lessonSubjectInfo);
                    }
            );
        }
        return lessonInfo;
    }

    @Override
    @Transactional
    public void updateLessonInfo(LessonInfo lessonInfo, String operaUserId) {
        lessonInfo.setCreateUserId(null);
        lessonInfo.setOperaUserId(operaUserId);
        lessonInfoMapper.updateByPrimaryKeySelective(lessonInfo);
        List<LessonSubjectInfo> update = lessonInfo.getSubjectInfos();

            List<LessonSubjectInfo> older = lessonSubjectInfoMapper.getByLessonId(lessonInfo.getId());
            Map<Integer,LessonSubjectInfo> olderMap = older.stream().collect(Collectors.toMap(LessonSubjectInfo::getId,s->s));
            List<LessonSubjectInfo> needInsert = update.stream().filter(s -> s.getId() == null).collect(Collectors.toList());
            List<LessonSubjectInfo> needUpdate = update.stream().filter(s -> s.getId() != null).collect(Collectors.toList());
            List<LessonSubjectInfo> needDelete = older.stream().filter(s -> !update.contains(s)).collect(Collectors.toList());
            if (!CollectionUtils.isEmpty(needDelete)) {
                lessonSubjectInfoService.needDelete(needDelete, operaUserId, lessonInfo.getId());
            }
            if (!CollectionUtils.isEmpty(needUpdate)) {
                lessonSubjectInfoService.needUpdate(needUpdate, operaUserId, lessonInfo.getId());
            }
            if (!CollectionUtils.isEmpty(needInsert)) {
                lessonSubjectInfoService.needInsert(needInsert, operaUserId, lessonInfo.getId());
            }

        logger.info("修改课程 lessonInfo={},res={}", JSONObject.toJSONString(lessonInfo), true);
    }

    @Override
    public LessonSubjectInfo addSubject(LessonSubjectInfo lessonSubjectInfo, String operaUserId) {
        lessonSubjectInfoMapper.insertSelective(lessonSubjectInfo);
        return lessonSubjectInfo;
    }

    @Override
    public void updateSubject(LessonSubjectInfo lessonSubjectInfo, String operaUserId) {
        lessonSubjectInfoMapper.updateByPrimaryKeySelective(lessonSubjectInfo);
    }

    @Override
    public void deleteSubject(Integer id, String operaUserId) {
        lessonSubjectInfoMapper.deleteByPrimaryKey(id);
    }

    @Override
    public void deleteLessonInfo(Integer id) {
        LessonInfo lessonInfo = new LessonInfo();
        lessonInfo.setId(id);
        lessonInfo.setIfOnShelf(false);
        lessonInfoMapper.updateByPrimaryKeySelective(lessonInfo);
        logger.info("删除课程 id={},res={}", id, true);
    }

    @Override
    public List<LessonInfo> getByCreateUserIds(List<String> createUserIds) {
        return lessonInfoMapper.getLessonInfoByCreateUserIds(createUserIds);
    }

    @Override
    public PageData getByCreateUserIds(LessonPageBean lessonPageBean, List<String> createUserIds) {
        List<String> schoolCompusList = new ArrayList<>();
        List<Boolean> statusList = new ArrayList<>();
        List<String> examList = new ArrayList<>();
        if (lessonPageBean.getSchoolCompus() != null && lessonPageBean.getSchoolCompus().length > 0) {
            schoolCompusList = Arrays.asList(lessonPageBean.getSchoolCompus());
        }
        if (lessonPageBean.getStatus() != null && lessonPageBean.getStatus().length > 0) {
            statusList = Arrays.asList(lessonPageBean.getStatus());
        }
        if (lessonPageBean.getExam() != null && lessonPageBean.getExam().length > 0) {
            examList = Arrays.asList(lessonPageBean.getExam());
        }
        PageHelper.startPage(lessonPageBean.getPage(), lessonPageBean.getRows());
        PageHelper.orderBy("if_on_shelf desc,create_time desc");
        List<LessonInfo> lessonInfos = lessonInfoMapper.getLesson(schoolCompusList, statusList, examList, createUserIds, lessonPageBean.getType());
        PageInfo<LessonInfo> pageInfo = new PageInfo<>(lessonInfos);
        pageInfo.getList().stream().forEach(
                lessonInfo -> {
                    lessonInfo.setExamName(ExamTypeEnum.getDescription(lessonInfo.getExam()));
                }
        );
        return PageDataUtil.getPageData(pageInfo);
    }

    @Override
    public PageData getByCreateUserIdsAndSearch(LessonPageBean lessonPageBean, List<String> createUserIds) {
        String query = lessonPageBean.getQuery();
        ExamTypeEnum e = ExamTypeEnum.getEnumByDescription(query);
        if (e != null) {
            query = e.name();
        }
        PageHelper.startPage(lessonPageBean.getPage(), lessonPageBean.getRows());
        PageHelper.orderBy("if_on_shelf desc,create_time desc");
        List<LessonInfo> lessonInfos = lessonInfoMapper.getLessonInfoByNameOrExam(query, createUserIds);
        PageInfo<LessonInfo> pageInfo = new PageInfo<>(lessonInfos);
        pageInfo.getList().stream().forEach(
                lessonInfo -> {
                    lessonInfo.setExamName(ExamTypeEnum.getDescription(lessonInfo.getExam()));
                }
        );
        return PageDataUtil.getPageData(pageInfo);
    }

    @Override
    public void updateLessonIfOnShelf(Integer lessonId, Boolean ifOnShelf, String operaUserId) {
        LessonInfo update = new LessonInfo();
        update.setId(lessonId);
        update.setIfOnShelf(ifOnShelf);
        lessonInfoMapper.updateByPrimaryKeySelective(update);
        logger.info("上下架课程 lessonId={},ifOnShelf={},operaUserId={}", lessonId, ifOnShelf, operaUserId);
    }

    @Override
    public List<LessonInfo> getAllLessonOnShelf() {
        return lessonInfoMapper.getLessonIfOnShelf(true);
    }

}
